﻿'   ScaledSkin.vb
'   WireBear Awesemulator
'
'   Created by Chris Kent
'   Copyright 2011 WireBear. All rights reserved
'
#Region "License Information"
'   WireBear Awesemulator is free software: you can redistribute it and/or modify
'   it under the terms of the GNU General Public License as published by
'   the Free Software Foundation, either version 3 of the License, or
'   (at your option) any later version.
'
'   WireBear Awesemulator is distributed in the hope that it will be useful,
'   but WITHOUT ANY WARRANTY; without even the implied warranty of
'   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
'   GNU General Public License for more details.
'
'   You should have received a copy of the GNU General Public License
'   along with WireBear Awesemulator - License.txt
'   If not, see <http://www.gnu.org/licenses/>.
#End Region


Public Class ScaledSkin

    Public Sub New(ByVal Skin As Skin, ByVal emulator As Emulator, ByVal useLandscapeLeft As Boolean, ByVal hWnd As IntPtr, AddStats As Boolean)
        _OriginalSkin = Skin

        Dim EmulatorSize As Size = ScreenShot.WindowSize(hWnd)
        If EmulatorSize.Height >= EmulatorSize.Width Then IsPortrait = True

        Dim eh As ScaledLayoutHelper
        If IsPortrait Then
            _hRatio = EmulatorSize.Height / emulator.Size.Height
            _wRatio = EmulatorSize.Width / emulator.Size.Width
            If emulator.Helpers.ContainsKey(FriendlyRatio) Then
                eh = emulator.Helpers(FriendlyRatio)
            Else
                eh = New ScaledLayoutHelper
            End If
            _screen = New Rectangle(New Point(emulator.ScreenPortrait.Left * _wRatio + eh.OffsetX, emulator.ScreenPortrait.Top * _hRatio + eh.OffsetY), New Size(emulator.ScreenPortrait.Width * _wRatio + eh.OffsetWidth, emulator.ScreenPortrait.Height * _hRatio + eh.OffsetHeight))
        Else
            _hRatio = EmulatorSize.Height / emulator.Size.Width
            _wRatio = EmulatorSize.Width / emulator.Size.Height
            If emulator.Helpers.ContainsKey(FriendlyRatio) Then
                eh = emulator.Helpers(FriendlyRatio)
            Else
                eh = New ScaledLayoutHelper
            End If
            _screen = New Rectangle(New Point(emulator.ScreenLandscape(useLandscapeLeft).Left * _wRatio + eh.OffsetY, emulator.ScreenLandscape(useLandscapeLeft).Top * _hRatio + eh.OffsetX), New Size(emulator.ScreenLandscape(useLandscapeLeft).Width * _wRatio + eh.OffsetHeight, emulator.ScreenLandscape(useLandscapeLeft).Height * _hRatio + eh.OffsetWidth))
        End If

        If Not _OriginalSkin.IsDummySkin Then
            'Adjust for Helpers
            Dim h As ScaledLayoutHelper
            If _OriginalSkin.Helpers.ContainsKey(FriendlyRatio) Then
                h = _OriginalSkin.Helpers(FriendlyRatio)
            Else
                h = New ScaledLayoutHelper()
            End If

            Using OriginalImage As New Bitmap(_OriginalSkin.ImagePath)
                If IsPortrait Then
                    _ScreenOrigin = New Point(_OriginalSkin.ScreenOrigin.X * _wRatio + h.OffsetX, _OriginalSkin.ScreenOrigin.Y * _hRatio + h.OffsetY)
                Else
                    If useLandscapeLeft Then
                        _ScreenOrigin = New Point(_OriginalSkin.ScreenOrigin.Y * _wRatio + h.OffsetY, (OriginalImage.Width - _OriginalSkin.ScreenOrigin.X) * _hRatio - _screen.Height - h.OffsetX)
                        OriginalImage.RotateFlip(RotateFlipType.Rotate90FlipXY)
                    Else
                        _ScreenOrigin = New Point((OriginalImage.Height - _OriginalSkin.ScreenOrigin.Y) * _wRatio - _screen.Width - h.OffsetY, _OriginalSkin.ScreenOrigin.X * _hRatio + h.OffsetX)
                        OriginalImage.RotateFlip(RotateFlipType.Rotate90FlipNone)
                    End If
                End If
                _Image = New Bitmap(CType(OriginalImage.Size.Width * _wRatio + IIf(IsPortrait, h.OffsetWidth, h.OffsetHeight), Integer), CType(OriginalImage.Size.Height * _hRatio + IIf(IsPortrait, h.OffsetHeight, h.OffsetWidth), Integer))
                Using g As Graphics = Graphics.FromImage(_Image)
                    g.SmoothingMode = Drawing2D.SmoothingMode.HighQuality
                    g.InterpolationMode = Drawing2D.InterpolationMode.HighQualityBicubic
                    g.PixelOffsetMode = Drawing2D.PixelOffsetMode.HighQuality
                    g.DrawImage(OriginalImage, New Rectangle(0, 0, _Image.Width, _Image.Height), 0, 0, OriginalImage.Width, OriginalImage.Height, GraphicsUnit.Pixel)

                    If AddStats Then
                        'Construct Stat strings
                        Dim stats As New Collections.Specialized.StringCollection
                        stats.Add(String.Format("~Zoom: {0}%", FriendlyRatio))
                        stats.Add(String.Format("Screen {0}: {1:N2}", IIf(h.OffsetX <= 0, "Left", "Right"), Math.Abs(h.OffsetX)))
                        stats.Add(String.Format("Screen {0}: {1:N2}", IIf(h.OffsetY < 0, "Up", "Down"), Math.Abs(h.OffsetY)))
                        stats.Add(String.Format("Skin {0}: {1:N2}", IIf(h.OffsetWidth < 0, "Thin", "Fat"), Math.Abs(h.OffsetWidth)))
                        stats.Add(String.Format("Skin {0}: {1:N2}", IIf(h.OffsetHeight < 0, "Short", "Tall"), Math.Abs(h.OffsetHeight)))

                        Using statFont As New Font("Arial", 8)
                            'Determine size of stat box
                            Dim maxWidth, boxHeight As Integer
                            Const LineSpacing As Integer = 12
                            For Each s As String In stats
                                Dim swidth As Integer = g.MeasureString(s, statFont, _Image.Width).Width
                                If swidth > maxWidth Then maxWidth = swidth
                                boxHeight += LineSpacing
                            Next
                            boxHeight += 2
                            Dim boxOrigin As New Point(_Image.Width - maxWidth, _Image.Height - boxHeight)
                            'Draw Stat Box (Lower-right corner)
                            g.FillRectangle(New SolidBrush(Color.FromArgb(27, 161, 226)), boxOrigin.X, boxOrigin.Y, maxWidth, boxHeight)

                            'Draw Stats directly on image (Regardless of zoom - stats are not scaled)
                            Dim lineY As Integer = boxOrigin.Y + 1
                            For Each s As String In stats
                                g.DrawString(s, statFont, Brushes.White, boxOrigin.X, lineY)
                                lineY += LineSpacing
                            Next
                        End Using
                    End If
                End Using
            End Using
        End If
    End Sub

    Private _OriginalSkin As Skin
    Public ReadOnly Property OriginalSkin() As Skin
        Get
            Return _OriginalSkin
        End Get
    End Property

    Private _hRatio As Double
    Public ReadOnly Property HeightRatio() As Double
        Get
            Return _hRatio
        End Get
    End Property

    Private _wRatio As Double
    Public ReadOnly Property WidthRatio() As Double
        Get
            Return _wRatio
        End Get
    End Property

    Public Function FriendlyRatio() As Integer
        Select Case _hRatio
            Case Is < 0.42
                Return 33
            Case Is <= 0.58
                Return 50
            Case Is < 0.7
                Return 66
            Case Is <= 0.88
                Return 75
            Case Else
                Return 100
        End Select
    End Function

    Private _Image As Bitmap
    Public ReadOnly Property Image() As Bitmap
        Get
            Return _Image
        End Get
    End Property

    Private _ScreenOrigin As Point
    Public ReadOnly Property ScreenOrigin() As Point
        Get
            Return _ScreenOrigin
        End Get
    End Property

    Private _screen As Rectangle
    Public ReadOnly Property Screen() As Rectangle
        Get
            Return _screen
        End Get
    End Property

    Public Property IsPortrait() As Boolean

End Class
